package main

import (
	"camp_lucky_draw/client/client_service"
	"camp_lucky_draw/entity"
	"encoding/json"
	"flag"
	"fmt"
	"io/ioutil"
	"log"
	"math/rand"
	"os"
	"path/filepath"
	"time"
)

/**
* @author aFun
* @data 2025/4/15 9:43
* @email: afunaaa222@163.com / 1030935903
* @address: Guangdong University of Technology, China
 */

// 全自动模拟客户端抽奖、领奖
func AutoClient(roleId uint) (rm *entity.ReportMetrics) {
	defer func() {
		if r := recover(); r != nil {
			//fmt.Printf("role_id:%d panic recovered:%v\n", roleId, r)
		}
	}()

	logFileName := fmt.Sprintf("./auto_client_logger/log_role_%d.txt", roleId)
	file, err := os.OpenFile(logFileName, os.O_CREATE|os.O_APPEND|os.O_WRONLY, 0666)
	if err != nil {
		//fmt.Printf("无法创建日志文件: %v\n", err)
		os.Exit(1)
	}
	logger := log.New(file, "", log.LstdFlags|log.Lshortfile)
	logger.Printf("roleId:%d\n", roleId)

	up := &client_service.UserProcess{}
	err = up.Enter_world(roleId, false)
	if err != nil {
		//fmt.Printf("role_id = %d 启动失败 err = %s\n", roleId, err.Error())
		return
	}

	metrics := &entity.Metrics{StartTime: time.Now()}

	opt := []int{1, 2, 3, 4, 5, 6}
	rand.Seed(time.Now().UnixNano())
	timeout := time.After(30 * time.Minute)
	for {
		select {
		case <-timeout:
			report := metrics.Report()
			return report
		default:
			SleepTime := rand.Intn(2)
			time.Sleep(time.Duration(SleepTime) * time.Second)
			// 一直执行
			seleted := opt[rand.Intn(len(opt))]
			var opErr error
			var start = time.Now()
			switch seleted {
			case 1:
				logger.Printf("role_id = %d 执行了请求用户数据\n", roleId)
				opErr = client_service.Eoutput_self_lucky_draw_data()
				printErr(roleId, "请求用户数据", opErr, logger)
			case 2:
				logger.Printf("role_id = %d 执行了请求层奖励数据\n", roleId)
				opErr = client_service.Eoutput_floor_lucky_draw_data()
				printErr(roleId, "请求层奖励数据", opErr, logger)
			case 3:
				logger.Printf("role_id = %d 执行了请求了累计奖励数据\n", roleId)
				opErr = client_service.Eoutput_cumulative_lucky_draw_data()
				printErr(roleId, "请求累计奖励数据", opErr, logger)
			case 4:
				// 模拟扭蛋
				pro := rand.Intn(100)
				if pro < 5 {
					// 5%的概率普通抽奖
					logger.Printf("role_id = %d 执行了普通扭蛋\n", roleId)
					opErr = client_service.Edraw(false)
					printErr(roleId, "扭蛋", opErr, logger)
				} else {
					// 95%的概率保护抽奖
					logger.Printf("role_id = %d 执行了保护扭蛋\n", roleId)
					opErr = client_service.Edraw(true)
					printErr(roleId, "扭蛋", opErr, logger)
				}
			case 5:
				// 模拟领取层奖励
				floor := client_service.CurUser.Role.Lucky_draw.Cur_floor
				pro := rand.Intn(100)
				if pro < 10 {
					// 正确领奖
					logger.Printf("role_id = %d 执行了领取层奖励\n", roleId)
					opErr = client_service.Eget_floor_reward(floor, 0)
					printErr(roleId, "领取层奖励", opErr, logger)
				} else {
					// 可能错误领奖
					logger.Printf("role_id = %d 执行了领取层奖励\n", roleId)
					opErr = client_service.Eget_floor_reward(floor, 1)
					printErr(roleId, "领取层奖励", opErr, logger)
				}
			case 6:
				// 模拟领取累计奖励
				indexes := []int64{}
				for i := 0; i < 5; i++ {
					indexes = append(indexes, int64(rand.Intn(50)+1)) // 1-50 其中只有1-30合法
				}
				logger.Printf("role_id = %d 执行了领取累计奖励, 领取奖励列表为：%v\n", roleId, indexes)
				opErr = client_service.Eget_cumulative_reward(indexes)
				printErr(roleId, "领取累计奖励", opErr, logger)
			}
			duration := time.Since(start)
			if opErr != nil {
				logger.Printf("role_id = %d 错误: %v\n", roleId, opErr)
				metrics.Record(false, duration)
			} else {
				metrics.Record(true, duration)
			}
		}
	}
}

func printErr(roleId uint, str string, err error, logger *log.Logger) {
	if err != nil {
		logger.Printf("role_id = %d 执行%s失败 err=%s\n", roleId, str, err.Error())
	}
}

func clearFolder(path string) error {
	entries, err := ioutil.ReadDir(path)
	if err != nil {
		return err
	}
	for _, entry := range entries {
		err = os.RemoveAll(filepath.Join(path, entry.Name()))
		if err != nil {
			return err
		}
	}
	return nil
}

func main() {
	role_id := flag.Int("role_id", 0, "角色ID")
	flag.Parse()
	rm := AutoClient(uint(*role_id))
	data, _ := json.Marshal(rm)
	fmt.Print(string(data))
}
